require "Common/define"
require "Logic/Config"
require "Common/functions"


---@class MapManager
MapManager = {};
local this = MapManager;
local curMapId = 0;
local curLastMapId = 101;
local mapCfg = nil;
local mapNextCfg = nil;
local mapStageNum = {};
local mapUnLockCfg = {};
local autoMapId = 101
MapManager.DungeonTaskTable={}

function MapManager.init()
    local cfg = G.dataTable["t_stage"];
    local idx = nil
    for k,v in pairs(cfg) do
        idx = v.f_ChapterId;
        mapStageNum[idx] = mapStageNum[idx]==nil and 1 or mapStageNum[idx] + 1;
        if v.f_UnlockText ~= "" then
            table.insert(mapUnLockCfg,v);
        end
    end
    table.sort(mapUnLockCfg,function (a,b)
        return a.f_StageId < b.f_StageId;
    end)
    this.preRewardChapter = 1
    return this;
end
function MapManager.SetBattleBeforeMapId(mapId)
    this.battleBeforeMapId = mapId
end
function MapManager.GetBattleBeforeMapId()
    return this.battleBeforeMapId or 0
end
function MapManager.setMapId(mapId)
    if curMapId ~= mapId then
        curLastMapId = curMapId;
    end
    curMapId = mapId;
    --log("mapId:"..mapId);
    mapCfg = G.dataTable["t_stage"][tostring(curMapId)];
    if mapCfg == nil then
        logError("找不到关卡t_state, id : "..curMapId)
        return
    end
    logicMgr.TAManager.UserSet("current_dungeon", MapManager.GetCurrentStage())
    mapNextCfg = G.dataTable["t_stage"][tostring(mapCfg.f_NextStage)];
end

function MapManager.SetetAutoMapId(mapId)
    autoMapId = mapId
end

function MapManager.GetAutoMapId()
    return autoMapId
end

function MapManager.GetMapcfgByID(mapId)
    return G.dataTable["t_stage"][tostring(mapId)];
end

function MapManager.getMapId()
    return curMapId;
end

function MapManager.getMapUnLockCfg()
    return mapUnLockCfg;
end

--最后一关
function MapManager.IsEndChapterMapId(id)
    local current = dataTable.getDataTableByStringId("t_stage",id)
    if current and current.f_NextStage > 0 then
        local next = dataTable.getDataTableByStringId("t_stage",current.f_NextStage)
        if next and next.f_ChapterId ~= current.f_ChapterId then
            return true
        end
    end
    if current and current.f_NextStage == -1 then
        return true
    end
    return false
end
--当前主线关卡播放的背景音乐
function MapManager.GetBGMByMapId(mapId)
    local _bgmId = 8        --常规战斗
    local _current = dataTable.getDataTableByStringId("t_stage",mapId)
    if _current and _current.f_Bgm then
        _bgmId = _current.f_Bgm
    end
    return _bgmId
end

--当前主线关卡能否跳关
function MapManager.SetIsCanSkip(flag)
    this.isCanSkip = flag;
end

function MapManager.GetIsCanSkip()
    return this.isCanSkip;
end

--获取章节最大stage配置
function MapManager.GetChapterMaxStageNum(chapter)
    local localChapter = chapter * 100;
    for i = 1, 100 do
        local mapId = localChapter + i;
        local current = dataTable.getDataTableByStringId("t_stage",mapId)
        if current ~= nil then
            if current.f_NextStage > 0 then
                local next = dataTable.getDataTableByStringId("t_stage",current.f_NextStage)
                if next and next.f_ChapterId ~= current.f_ChapterId then
                    return current;
                end
            else
                return current;
            end
        end
    end
    return nil;
end

function MapManager.HasChapterRewardByPre()
    if curMapId == 0 then
        return false,1
    end
    local flag = logicMgr.GuideMgr.HasGuidingGotoBattle()
    if flag then
        return false,1
    end
    this.InitChapterCfgList()
    local stageCfg = dataTable.getDataTableByStringId("t_stage",curMapId)
    if not stageCfg then return nil end
    local chapter = stageCfg.f_ChapterId
    local pre = this.preRewardChapter
    while(pre < chapter) do
        local taskTable = this.chapterRewardCfgList[pre]
        if taskTable then
            local serverData = logicMgr.TaskManager.getTaskServerDataById(taskTable.f_TaskId);
            if serverData and (serverData.status == 1 or serverData.status == 0) then--未领取
                this.preRewardChapter = pre
                return true,pre
            end
        end
        pre = pre + 1
    end
    this.preRewardChapter = chapter - 1
    return false,chapter
end
function MapManager.InitChapterCfgList()
    if this.chapterRewardCfgList == nil then
        local taskConfig = logicMgr.TaskManager.getChapterCfgList(EnumConst.AchieveTaskType.Chapter);
        this.chapterRewardCfgList = {}
        this.preRewardChapter = 1
        for k, v in  pairs(taskConfig) do
            this.chapterRewardCfgList[v.f_Progress] = v
        end
    end
end
function MapManager.GetChapterRewardCfg(chapter)
    this.InitChapterCfgList()
    return this.chapterRewardCfgList[chapter]
end

function MapManager.GetChapterRewardByChapter(chapter)
    this.InitChapterCfgList()
    local taskTable = this.chapterRewardCfgList[chapter]
    local hasReward = false
    local rewardGet = false
    if taskTable then
        hasReward = true
        local serverData = logicMgr.TaskManager.getTaskServerDataById(taskTable.f_TaskId);
        if serverData == nil then
            --任务找不到往后查任务
            local preC = math.max(chapter - 1,1)--往前查一章
            local nextC = chapter + 1 --往后查一章
            local preChapter = this.chapterRewardCfgList[preC]
            local data = logicMgr.TaskManager.getTaskServerDataById(preChapter.f_TaskId)
            if data then
                return true,false,taskTable
            end
            local nextChapter = this.chapterRewardCfgList[nextC]
            if nextChapter then
                local data = logicMgr.TaskManager.getTaskServerDataById(nextChapter.f_TaskId)
                if data then--表明当前该任务已领取
                    return true,true,taskTable
                end
            else--最后一章
                return false,false,taskTable
            end
            return true,false,taskTable
        end
        if serverData.status == -1 then --已领取
            rewardGet = true
        end
    end
    return hasReward,rewardGet,taskTable
end
--章节关卡宝箱是否领取
function MapManager.GetChapterReward(levelId)
    local stageCfg = dataTable.getDataTableByStringId("t_stage",levelId)
    if not stageCfg then return nil end
    local chapter = stageCfg.f_ChapterId
    return this.GetChapterRewardByChapter(chapter)
end
function MapManager.getMapcfg()
    return mapCfg;
end
function MapManager.getNextMapcfg()
    return mapNextCfg;
end

function MapManager.getLastMapcfg()
    for i, v in pairs(G.dataTable["t_stage"]) do
        if v.f_NextStage == curMapId then
            return v.f_StageId;
        end
    end
    return curLastMapId;
end

function MapManager.getMapStageNumById(id)
    local data = this.GetMapcfgByID(id);
    if data == nil then
        return 0;
    end
    return mapStageNum[data.f_ChapterId];
end

function MapManager.getMapStageNumByChapter(id)
    if id == nil then
        return 0;
    end
    return mapStageNum[id] or 0;
end

function MapManager.getMapName()
    if mapCfg ~= nil then
        return getLanguage(mapCfg.f_StageName);
    end
    return nil;
end

function MapManager.getBattleMapName()
    if mapCfg ~= nil then
        return mapCfg.f_AutoFightMap;
    end
    return nil;
end

function MapManager.getBossMapName()
    if mapCfg ~= nil then
        return mapCfg.f_BattleMap;
    end
    return nil;
end

function MapManager.getNextStage()
    if mapCfg ~= nil then
        return tonumber(mapCfg.f_NextStage);
    end
    return 0;
end
function MapManager.GetCurrentStage()
    if mapCfg ~= nil then
        return tonumber(mapCfg.f_StageId);
    end
    return 0;
end
function MapManager.GetCurrentChapterId()
    if mapCfg ~= nil then
        return tonumber(mapCfg.f_ChapterId);
    end
    return 0
end

function MapManager.getMaxTime()
    if mapNextCfg ~= nil then
        return tonumber(mapNextCfg.f_MaxTime);
    end
    return 90;
end

-- 获取关卡需要多少挑战队伍,默认获取下一关卡
function MapManager.getStageNeedTeamNum(id)
    if id == nil then
        id = this.getNextStage()
    end
    if id < 0 then
        return -1;
    end
    local data = this.GetMapcfgByID(id);
    if data ~= nil then
        local list = decodeJsonStrToTabel(data.f_MonsterTeamId);
        if list then
            return #list;
        else
            return 1;
        end
    end
    return 1;
end

-- 获取关卡需要多少挑战队伍,默认获取下一关卡
function MapManager.getStoryBattleNeedTeamNum(id)
    id = id or dungeonHandler.hardData.maxPassDungeon
    if id == 0 then
        return #G.dataTable["t_stagehardmode"]["101"].f_MonsterTeamId
    else
        return #G.dataTable["t_stagehardmode"][tostring(G.dataTable["t_stagehardmode"][tostring(id)].f_NextStage)].f_MonsterTeamId
    end
end
function MapManager.isOpenNewChapter()
    local nowTableData = this.GetMapcfgByID(this.getMapId());
    local nextTableData = this.GetMapcfgByID(this.getNextStage());
    if nowTableData and nextTableData then
        return nowTableData.f_ChapterId ~= nextTableData.f_ChapterId;
    else
        return false
    end
end


function MapManager.getMonster()
    local monsterList = {}
    if mapNextCfg ~= nil then
        local monsterTableList = decodeJsonStrToTabel(mapNextCfg.f_MonsterTeamId);
        for k, v in pairs(monsterTableList) do
            local monsters = {};
            monsters.team = {};
            local monsterteamCfg = dataTable.getDataTableByStringId("t_monsterteam",v);
            monsters.occupation = monsterteamCfg.f_occupation;
            monsters.power = monsterteamCfg.f_Combat_Effectiveness;
            if monsterteamCfg ~= nil then
                if monsterteamCfg.f_MonsterPara1 ~= nil and monsterteamCfg.f_MonsterPara1 ~= "" then
                    monsterPara = decodeJsonStrToTabel(monsterteamCfg.f_MonsterPara1);
                    if monsterPara[1] > 0 then
                        monsters.team[1] = monsterPara;
                    end
                end
                if monsterteamCfg.f_MonsterPara2 ~= nil and monsterteamCfg.f_MonsterPara2 ~= "" then
                    monsterPara = decodeJsonStrToTabel(monsterteamCfg.f_MonsterPara2);
                    if monsterPara[1] > 0 then
                        monsters.team[2] = monsterPara;
                    end
                end
                if monsterteamCfg.f_MonsterPara3 ~= nil and monsterteamCfg.f_MonsterPara3 ~= "" then
                    monsterPara = decodeJsonStrToTabel(monsterteamCfg.f_MonsterPara3);
                    if monsterPara[1] > 0 then
                        monsters.team[3] = monsterPara;
                    end
                end
                if monsterteamCfg.f_MonsterPara4 ~= nil and monsterteamCfg.f_MonsterPara4 ~= "" then
                    monsterPara = decodeJsonStrToTabel(monsterteamCfg.f_MonsterPara4);
                    if monsterPara[1] > 0 then
                        monsters.team[4] = monsterPara;
                    end
                end
                if monsterteamCfg.f_MonsterPara5 ~= nil and monsterteamCfg.f_MonsterPara5 ~= "" then
                    monsterPara = decodeJsonStrToTabel(monsterteamCfg.f_MonsterPara5);
                    if monsterPara[1] > 0 then
                        monsters.team[5] = monsterPara;
                    end
                end
                if monsterteamCfg.f_MonsterPara6 ~= nil and monsterteamCfg.f_MonsterPara6 ~= "" then
                    monsterPara = decodeJsonStrToTabel(monsterteamCfg.f_MonsterPara6);
                    if monsterPara[1] > 0 then
                        monsters.team[6] = monsterPara;
                    end
                end
            end
            table.insert(monsterList, monsters);
        end
    end
    return monsterList;
end

function MapManager.getHardMonster(flagid)
    local monsterList = {}
    local mapnextCfg = {}
    local cfg = G.dataTable["t_stagehardmode"]
    local id = dungeonHandler.hardData.maxPassDungeon
    -- mapnextCfg = cfg[tostring(flagid)] -- 需要删除
    -- if  id== 0 then
    --     mapnextCfg = cfg["101"]
    -- else
    --     mapnextCfg = cfg[tostring(cfg[tostring(flagid).f_NextStage])]
    --     if mapnextCfg == -1 then
    --         mapnextCfg = cfg[tostring(cfg[tostring(flagid).f_Id])]
    --     end
    -- end
    mapnextCfg = cfg[tostring(flagid)]
    if mapnextCfg ~= nil then
        local monsterTableList = decodeJsonStrToTabel(mapnextCfg.f_MonsterTeamId);
        for k, v in pairs(monsterTableList) do
            local monsters = {};
            monsters.team = {};
            --  local monsterteamCfg = G.dataTable["t_monsterteam"][tostring(v)];
            local monsterteamCfg = dataTable.getDataTableByStringId("t_stagehardmonsterteam",v);   -- 这个才是剧情模式配置表
            monsters.occupation = monsterteamCfg.f_occupation;
            monsters.power = monsterteamCfg.f_Combat_Effectiveness;
            if monsterteamCfg ~= nil then
                if monsterteamCfg.f_MonsterPara1 ~= nil and monsterteamCfg.f_MonsterPara1 ~= "" then
                    monsterPara = decodeJsonStrToTabel(monsterteamCfg.f_MonsterPara1);
                    if monsterPara[1] > 0 then
                        monsters.team[1] = monsterPara;
                    end
                end
                if monsterteamCfg.f_MonsterPara2 ~= nil and monsterteamCfg.f_MonsterPara2 ~= "" then
                    monsterPara = decodeJsonStrToTabel(monsterteamCfg.f_MonsterPara2);
                    if monsterPara[1] > 0 then
                        monsters.team[2] = monsterPara;
                    end
                end
                if monsterteamCfg.f_MonsterPara3 ~= nil and monsterteamCfg.f_MonsterPara3 ~= "" then
                    monsterPara = decodeJsonStrToTabel(monsterteamCfg.f_MonsterPara3);
                    if monsterPara[1] > 0 then
                        monsters.team[3] = monsterPara;
                    end
                end
                if monsterteamCfg.f_MonsterPara4 ~= nil and monsterteamCfg.f_MonsterPara4 ~= "" then
                    monsterPara = decodeJsonStrToTabel(monsterteamCfg.f_MonsterPara4);
                    if monsterPara[1] > 0 then
                        monsters.team[4] = monsterPara;
                    end
                end
                if monsterteamCfg.f_MonsterPara5 ~= nil and monsterteamCfg.f_MonsterPara5 ~= "" then
                    monsterPara = decodeJsonStrToTabel(monsterteamCfg.f_MonsterPara5);
                    if monsterPara[1] > 0 then
                        monsters.team[5] = monsterPara;
                    end
                end
                if monsterteamCfg.f_MonsterPara6 ~= nil and monsterteamCfg.f_MonsterPara6 ~= "" then
                    monsterPara = decodeJsonStrToTabel(monsterteamCfg.f_MonsterPara6);
                    if monsterPara[1] > 0 then
                        monsters.team[6] = monsterPara;
                    end
                end
            end
            table.insert(monsterList, monsters);
        end
    end
    return monsterList;
end

function MapManager.GetMapNameByFightType(fightType)
    if fightType == EnumConst.FightTypeConst.DUNGEON or fightType == EnumConst.FightTypeConst.GuildBoss or
            fightType == EnumConst.FightTypeConst.Plunder or fightType == EnumConst.FightTypeConst.GuildBattlePlus or
            fightType == EnumConst.FightTypeConst.RankBattle or fightType == EnumConst.FightTypeConst.FormationEditor or
            fightType == EnumConst.FightTypeConst.DungeonEventPK or fightType == EnumConst.FightTypeConst.SoloChaosTest then
        return this.getBattleMapName();
    elseif fightType == EnumConst.FightTypeConst.TOWER then
        return logicMgr.TowerManager.getBattleMapId()
    elseif fightType == EnumConst.FightTypeConst.ARENA or fightType == EnumConst.FightTypeConst.ARENARECORD or
            fightType == EnumConst.FightTypeConst.FriendAttack or fightType == EnumConst.FightTypeConst.FriendDefend or
            fightType == EnumConst.FightTypeConst.FriendCompeteBattle or fightType == EnumConst.FightTypeConst.GuildFriendCompeteBattle then
        return G.dataTable["t_global"]["134"]["f_string_value"]
    elseif fightType == EnumConst.FightTypeConst.INSTANCE then
        return "AutoFightMap38"
    elseif fightType == EnumConst.FightTypeConst.TRIAL then
        return logicMgr.TrialsManager.GetTrialsConfig()[tostring(logicMgr.TrialsManager.GetTrialsInfo().trialsId)].f_BattleMap;
    elseif fightType == EnumConst.FightTypeConst.Expedition then
        return ExpeditionMapMgr.GetMapName()
    elseif fightType == EnumConst.FightTypeConst.DarkStreet then
        return dataTable.getDataTableByStringId("t_mapdarklane",1).f_Name
    elseif fightType == EnumConst.FightTypeConst.StoryBattle then
        return logicMgr.StoryHardManager.getBattleMapName()
    elseif fightType == EnumConst.FightTypeConst.LongJourneyHell then
        return logicMgr.LongJourneyHellManager.getBattleMapName()
    end
end

function MapManager.SetStoryHardAutoMapId(mapId, groupId)
    this.storyHardAutoMapId = mapId
    this.storyHardAutoGroupId = groupId
end

function MapManager.GetStoryHardAutoMapId()
    return this.storyHardAutoMapId, this.storyHardAutoGroupId or 1;
end
return MapManager